﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint;
using ConsolidationTool.Common;

namespace ConsolidationTool.WebParts.Layouts.AjaxServices
{
    public class CalcServices : IAjaxService
    {
        /*
         * TODO
         * 改造成可以支持取YTD的值。不仅仅是Rolling 12 Month
         */
        private RateServices rateServices;
        SPList list;
        List<CacheSPItem> listItems;

        public AjaxResult Excute(System.Web.HttpContext httpContext, FSSearchEntity searchEntity)
        {
            list = SPContext.Current.Web.Lists[searchEntity.ListTitle];
            rateServices = new RateServices();

            DateTime date = DateTime.Parse(searchEntity.Year + "-" + searchEntity.Month + "-01");

            if (searchEntity.Type == "R_Actual_ICF_IC02060000_Rate")
            {
                return R_Actual_ICF_IC02060000_Rate(httpContext, searchEntity);
            }

            string[] fields = httpContext.Request["fields"].Split(',');

            DateTime startDate = date.AddMonths(-11);
            SPQuery query = new SPQuery();
            query.Query = string.Format(@"<Where>
                                            <Eq>
                                                <FieldRef Name='CoCd' />
                                                <Value Type='Text'>{0}</Value>
                                            </Eq>
                                        </Where>", searchEntity.CompanyCode);
            string message = "";

            var items = list.Items;
            int itemCount = 0;
            listItems = new List<CacheSPItem>();
            List<ExchangeRate> currentMonthAsiaRate = new List<ExchangeRate>();

            string data = searchEntity.Data;
            searchEntity.Data = "";


            searchEntity.Data += "{";

            if (data.Equals("ExchangeRate"))
            {
                // Group by Company name for Cumulative each month value with rolling 12 month
                currentMonthAsiaRate = rateServices.LoadExchangeRate("Actual", searchEntity.Year, searchEntity.Month, "Original");

                query.Query = string.Format(@"<Where>
      <And>
         <Eq>
            <FieldRef Name='Year' />
            <Value Type='Integer'>{0}</Value>
         </Eq>
         <Eq>
            <FieldRef Name='Month' />
            <Value Type='Integer'>{1}</Value>
         </Eq>
      </And>
   </Where>", searchEntity.Year, searchEntity.Month);
                items = list.GetItems(query);


                itemCount = items.Count;

                for (int i = 0; i < itemCount; i++)
                {
                    var item = items[i];
                    listItems.Add(new CacheSPItem(item));
                }
                itemCount = listItems.Count;


            }
            else
            {

                if (searchEntity.CompanyCode != "Asia")
                    items = list.GetItems(query);

                itemCount = items.Count;

                for (int i = 0; i < itemCount; i++)
                {

                    var item = items[i];
                    int Month = int.Parse(item["Month"] + "");
                    int year = int.Parse(item["Year"] + "");

                    if (year == date.Year && Month == date.Month) //这里去掉当月的是因为Invertory里面的当月要到当前页面上取
                        continue;

                    if ((year == startDate.Year && Month >= startDate.Month) || (year == date.Year && Month < date.Month))
                        listItems.Add(new CacheSPItem(item));
                }
                itemCount = listItems.Count;
            }
            bool success = itemCount > 0;


            fields.ToList().ForEach(p =>
            {
                decimal fieldValue = 0.00M;

                for (int i = 0; i < itemCount; i++)
                {
                    var item = listItems[i];
                    int month = int.Parse(item.Month + "");
                    if (data.Equals("ExchangeRate"))
                    {
                        decimal rolling12MonthValue = 0.00M;
                        item.Last12MonthItem.ForEach(l12 =>
                        {

                            rolling12MonthValue += BusinessService.decimalParse(l12[p]);
                        });

                        var rateItem = currentMonthAsiaRate.FirstOrDefault(c => c.FC == item.LocalCurrency);
                        rolling12MonthValue = Utilities.Division(rolling12MonthValue, BusinessService.decimalParse(rateItem.TryGetValue("CM") + ""));
                        fieldValue += rolling12MonthValue;
                        //var rolling12MonthValue = item.GetL12Value(
                        //    new ARTReportFromItem()
                        //    {
                        //        field = "CM",
                        //        identity = p,
                        //        list = searchEntity.ListTitle
                        //    },
                        //    new SearchEntity()
                        //    {
                        //        Entity = item.CoCd,
                        //        Year = int.Parse(searchEntity.Year),
                        //        Month = int.Parse(searchEntity.Month)
                        //    });
                    }
                    else
                    {
                        if (item.Year + "" == searchEntity.Year && month >= int.Parse(searchEntity.Month))
                            continue;
                        fieldValue += BusinessService.decimalParse(item[p] + "");
                    }
                }
                //if (searchEntity.Type == "Avg") 因为取不到当月数据，所以需要去页面上取，再算平均值。这里不能算。
                //{
                //    fieldValue = fieldValue / 12;
                //}

                searchEntity.Data += string.Format("\"{0}\":\"{1}\",", p, fieldValue);
            });

            searchEntity.Data = searchEntity.Data.Substring(0, searchEntity.Data.Length - 1);
            searchEntity.Data += "}";
            if (!success)
            {
                message = "can not find result ...";
                return new AjaxResult(false, searchEntity.Data) { FullMsg = message };
            }
            return new AjaxResult(true, searchEntity.Data) { FullMsg = "Successfull" };

        }

        private AjaxResult R_Actual_ICF_IC02060000_Rate(System.Web.HttpContext ctx, FSSearchEntity se)
        {
            decimal value = 0.00M, YTDvalue = 0.00M;
            var YTDlistItems = new List<CacheSPItem>();

            try
            {

                listItems = new List<CacheSPItem>();
                // Group by Company name for Cumulative each month value with rolling 12 month
                var lastYearDecAsiaRate = rateServices.LoadExchangeRate("Actual", se.ProcessData.AddYears(-1).Year + "", "12", "Original");
                var lastMonthAsiaRate = rateServices.LoadExchangeRate("Actual", se.ProcessData.AddMonths(-1).Year + "", se.ProcessData.AddMonths(-1).Month + "", "Original");
                var currentMonthAsiaRate = rateServices.LoadExchangeRate("Actual", se.Year, se.Month, "Original");
                var query = new SPQuery();
                query.Query = string.Format(@"<Where>
      <And>
         <Eq>
            <FieldRef Name='Year' />
            <Value Type='Integer'>{0}</Value>
         </Eq>
         <Eq>
            <FieldRef Name='Month' />
            <Value Type='Integer'>{1}</Value>
         </Eq>
      </And>
   </Where>", se.Year, se.Month);
                var items = list.GetItems(query);
                var itemCount = items.Count;

                for (int i = 0; i < itemCount; i++)
                {
                    var item = items[i];
                    listItems.Add(new CacheSPItem(item));
                }


                var ytdQuery = new SPQuery();
                ytdQuery.Query = string.Format(@"<Where>
      <And>
         <Eq>
            <FieldRef Name='Year' />
            <Value Type='Integer'>{0}</Value>
         </Eq>
         <Eq>
            <FieldRef Name='Month' />
            <Value Type='Integer'>1</Value>
         </Eq>
      </And>
   </Where>", se.Year);
               var  ytdItems = list.GetItems(ytdQuery);

               for (int i = 0; i < ytdItems.Count; i++)
                {
                    var item = ytdItems[i];
                    YTDlistItems.Add(new CacheSPItem(item));
                }
                YTDlistItems.ForEach(item =>
                {
                    if (item.Month == 1)
                    {
                        var lydRate = lastYearDecAsiaRate.FirstOrDefault(p => p.FC == item.LocalCurrency);
                        var cmRate = currentMonthAsiaRate.FirstOrDefault(p => p.FC == item.LocalCurrency);

                        decimal cmYTDRV = cmRate == null ? 0 : BusinessService.decimalParse(cmRate.YTD);
                        decimal lydYTDRV = lydRate == null ? 0 : BusinessService.decimalParse(lydRate.YTD);

                        //YTD value after exchange rate , need current month rate - last year dec rate 
                        decimal cmYTDV = Utilities.Division(BusinessService.decimalParse(item["CM_" + se.Fields]), cmYTDRV);
                        decimal lydYTDV = Utilities.Division(BusinessService.decimalParse(item["CM_" + se.Fields]), lydYTDRV);

                        YTDvalue += (cmYTDV - lydYTDV);
                    }
                });                
        
                listItems.ForEach(item =>
                {
                    var lydRate = lastYearDecAsiaRate.FirstOrDefault(p => p.FC == item.LocalCurrency);
                    var lmRate = lastMonthAsiaRate.FirstOrDefault(p => p.FC == item.LocalCurrency);
                    var cmRate = currentMonthAsiaRate.FirstOrDefault(p => p.FC == item.LocalCurrency);

                    decimal cmRV = cmRate == null ? 0 : BusinessService.decimalParse(cmRate.YTD);
                    decimal lmRV = lmRate == null ? 0 : BusinessService.decimalParse(lmRate.YTD);


                    //Current Month value after exchange rate
                    decimal cmV = Utilities.Division(BusinessService.decimalParse(item["CM_" + se.Fields]), cmRV);
                    decimal lmV = Utilities.Division(BusinessService.decimalParse(item["CM_" + se.Fields]), lmRV);
              

                    value += (cmV - lmV);
                });

                return new AjaxResult(true, new { CM = value, YTD = YTDvalue }) { FullMsg = "Successfull" };
            }
            catch (Exception ex)
            {
                return new AjaxResult(false, value) { FullMsg = ex.Message };
            }
        }
    }
}
